
#include "Z180.h"
#include "lcd.h"


#define Z180_RESET_HIGH HAL_GPIO_WritePin(PortReset, PinReset, GPIO_PIN_SET)
#define Z180_RESET_LOW  HAL_GPIO_WritePin(PortReset, PinReset, GPIO_PIN_RESET)


#define Z180_A0_HIGH    HAL_GPIO_WritePin(PortA0, PinA0, GPIO_PIN_SET)
#define Z180_A0_LOW     HAL_GPIO_WritePin(PortA0, PinA0, GPIO_PIN_RESET)


#define Z180_CS_HIGH    HAL_GPIO_WritePin(PortCS, PinCS, GPIO_PIN_SET)
#define Z180_CS_LOW     HAL_GPIO_WritePin(PortCS, PinCS, GPIO_PIN_RESET)


static uint8_t Height, Width;
static uint16_t offsetX=2, offsetY=1;
static SPI_HandleTypeDef *Hspi;
static GPIO_TypeDef *PortReset, *PortA0, *PortCS;
static uint16_t PinReset, PinA0, PinCS;



//========================================================
void  Z180_writeCommand(uint8_t c)
{
  Z180_A0_LOW;
  Z180_CS_LOW;
  HAL_SPI_Transmit(Hspi, &c, 1, 0);
  Z180_CS_HIGH;
}

//========================================================

void Z180_writeData(uint8_t dat)
{
  Z180_A0_HIGH;
  Z180_CS_LOW;
  HAL_SPI_Transmit(Hspi, &dat, 1, 0);
  Z180_CS_HIGH;
}


void Z180_writeDataMany(uint8_t count, uint8_t * dat)
{
  Z180_A0_HIGH;
  Z180_CS_LOW;
  HAL_SPI_Transmit(Hspi, dat, count, 0);
  Z180_CS_HIGH;
}


//========================================================
void Z180_setRegion(uint16_t x_start, uint16_t y_start, uint16_t x_end, uint16_t y_end)
{
  uint8_t x_params[] = {0x00, x_start + offsetX, 0x00, x_end + offsetX};
  uint8_t y_params[] = {0x00, y_start + offsetY, 0x00, y_end + offsetY};

   Z180_writeCommand(0x2A);
   Z180_writeDataMany(4, x_params);

   Z180_writeCommand(0x2B);
   Z180_writeDataMany(4, y_params);

   Z180_writeCommand(0x2C);
}

uint16_t Z180_getWidth(void)
{
  return Width;
}
uint16_t Z180_getHeight(void)
{
  return Height;
}


//========================================================
void  Z180_init(SPI_HandleTypeDef* hspi, GPIO_TypeDef *portReset, uint16_t pinReset, GPIO_TypeDef *portA0, uint16_t pinA0, 
                  GPIO_TypeDef *portCs, uint16_t pinCs, uint8_t rotate)
{
  Hspi = hspi;
  PortReset = portReset;
  PinReset = pinReset;
  PortA0 = portA0;
  PinA0 = pinA0;
  PortCS = portCs;
  PinCS = pinCs;
  //------------------------------------ST7735R Reset Sequence-----------------------------------------// 
  Z180_RESET_HIGH;
  HAL_Delay(1);
  Z180_RESET_LOW;
  HAL_Delay(1);
  Z180_RESET_HIGH;
  HAL_Delay(1);

  //--------------------------------End ST7735R Reset Sequence --------------------------------------// 

  //--------------------------------End ST7735S Reset Sequence --------------------------------------// 
  Z180_writeCommand(0x11); //Sleep out 
  // delay(120);              //Delay 120ms 
  //------------------------------------ST7735S Frame Rate-----------------------------------------// 
  Z180_writeCommand(0xB1); 
  Z180_writeData(0x05); 
  Z180_writeData(0x3C); 
  Z180_writeData(0x3C); 
  Z180_writeCommand(0xB2); 
  Z180_writeData(0x05); 
  Z180_writeData(0x3C); 
  Z180_writeData(0x3C); 
  Z180_writeCommand(0xB3); 
  Z180_writeData(0x05); 
  Z180_writeData(0x3C); 
  Z180_writeData(0x3C); 
  Z180_writeData(0x05); 
  Z180_writeData(0x3C); 
  Z180_writeData(0x3C); 

  //------------------------------------End ST7735S Frame Rate---------------------------------// 
  Z180_writeCommand(0xB4); //Dot inversion 
  Z180_writeData(0x03); 

  //------------------------------------ST7735S Power Sequence---------------------------------// 
  Z180_writeCommand(0xC0); 
  Z180_writeData(0x28); 
  Z180_writeData(0x08); 
  Z180_writeData(0x04); 
  Z180_writeCommand(0xC1); 
  Z180_writeData(0XC0); 
  Z180_writeCommand(0xC2); 
  Z180_writeData(0x0D); 
  Z180_writeData(0x00); 
  Z180_writeCommand(0xC3); 
  Z180_writeData(0x8D); 
  Z180_writeData(0x2A); 
  Z180_writeCommand(0xC4); 
  Z180_writeData(0x8D); 
  Z180_writeData(0xEE); 

  //---------------------------------End ST7735S Power Sequence-------------------------------------// 
  Z180_writeCommand(0xC5); //VCOM 
  Z180_writeData(0x1A); 

  //------------------------------------ST7735S Gamma Sequence---------------------------------// 
  Z180_writeCommand(0xE0); 
  Z180_writeData(0x04); 
  Z180_writeData(0x22); 
  Z180_writeData(0x07); 
  Z180_writeData(0x0A); 
  Z180_writeData(0x2E); 
  Z180_writeData(0x30); 
  Z180_writeData(0x25); 
  Z180_writeData(0x2A); 
  Z180_writeData(0x28); 
  Z180_writeData(0x26); 
  Z180_writeData(0x2E); 
  Z180_writeData(0x3A); 
  Z180_writeData(0x00); 
  Z180_writeData(0x01); 
  Z180_writeData(0x03); 
  Z180_writeData(0x13); 
  Z180_writeCommand(0xE1); 
  Z180_writeData(0x04); 
  Z180_writeData(0x16); 
  Z180_writeData(0x06); 
  Z180_writeData(0x0D); 
  Z180_writeData(0x2D); 
  Z180_writeData(0x26); 
  Z180_writeData(0x23); 
  Z180_writeData(0x27); 
  Z180_writeData(0x27); 
  Z180_writeData(0x25); 
  Z180_writeData(0x2D); 
  Z180_writeData(0x3B); 
  Z180_writeData(0x00); 
  Z180_writeData(0x01); 
  Z180_writeData(0x04); 
  Z180_writeData(0x13); 
  //------------------------------------End ST7735S Gamma Sequence-----------------------------// 
  Z180_writeCommand(0x3A); //65k mode 
  Z180_writeData(0x05); 
  Z180_writeCommand(0x36); //MX, MY, RGB mode 
  switch (rotate)
  {
    case LCD_ROTAGE_0:
      Z180_writeData(0xC0);
      Width = 128;
      Height = 160;
      offsetX = 2;
      offsetY = 1;
    break;
    case LCD_ROTAGE_90:
      Z180_writeData(0x60);
      Width = 160;
      Height = 128;
      offsetX = 1;
      offsetY = 2;
    break;
    case LCD_ROTAGE_180:
      Z180_writeData(0x00);
      Width = 128;
      Height = 160;
      offsetX = 2;
      offsetY = 1;
    break;
    case LCD_ROTAGE_270:
      Z180_writeData(0xA0);
      Width = 160;
      Height = 128;
      offsetX = 1;
      offsetY = 2;
    break;
  }

  Z180_writeCommand(0x29); //Display on 
 
  LCD_init(Z180_writeDataMany, Z180_setRegion, Z180_getWidth, Z180_getHeight);
} 



